from django.http import HttpResponse
from django.shortcuts import render
from rest_framework.viewsets import ReadOnlyModelViewSet, ModelViewSet
from .models import Label, Article, Comment
from .serializers import LabelSerializer, ArticleSerializer, CommentSerializer, SonCommentSerializer
from rest_framework.permissions import IsAuthenticated
from .paginations import ArticleLimitOffsetPagination, ArticlePageNumberPagination
from django.db.models import F
from rest_framework.decorators import action
from rest_framework.response import Response
from rest_framework import status


# Create your views here.
# 标签的视图类
class LabelViewSet(ReadOnlyModelViewSet):
    # 指定序列化器和模型
    queryset = Label.objects.all()
    serializer_class = LabelSerializer
    # 增加权限登录状态才可以
    permission_classes = [IsAuthenticated]


# 文章的视图类
class ArticleViewSet(ModelViewSet):
    # 指定模型和序列化器
    queryset = Article.objects.filter(is_delete=False)
    serializer_class = ArticleSerializer
    # 增加权限登录状态才可以
    permission_classes = [IsAuthenticated]
    # 指定分页器
    pagination_class = ArticleLimitOffsetPagination

    # 重写模型
    def get_queryset(self):
        if self.action in ['list', 'retrieve']:
            return self.queryset.filter(status=1)
        else:
            return self.queryset

    # 重写序列化器
    def get_serializer_class(self):
        if self.action == 'comment':
            return CommentSerializer
        else:
            return ArticleSerializer

    # 重写create方法,不然会导致用户id和文章不对应(即他人可以发非本人的文章)
    def create(self, request, *args, **kwargs):
        # 允许修改传入的post数据
        request.POST._mutable = True
        # 写死现在的id为目前的登录用户id
        request.data['user'] = request.user.id
        return ModelViewSet.create(self, request, *args, **kwargs)

    # 重写retrieve方法,每次点击使得浏览量加1
    def retrieve(self, request, *args, **kwargs):
        # 获取当前文章的id,id值存储在kwargs之中
        article_id = kwargs.get('pk')
        article = self.get_queryset().filter(id=article_id)
        # 进行修改
        article.update(page_view=F('page_view') + 1)
        return ModelViewSet.retrieve(self, request, *args, **kwargs)

    # 获取当前文章的一级评论用于展示
    @action(methods=['get'], detail=True)
    def comment(self, request, pk=None):
        # 尝试获取这一个文章的信息
        try:
            article = self.get_queryset().get(id=pk)
        except Article.DoesNotExist:
            return Response(status=status.HTTP_404_NOT_FOUND)
        # 从文章中去获取内容,是为反向查询
        comments = article.comment_set.filter(parent_comment=None)
        # 进行分页
        page = self.paginate_queryset(comments)
        # 返回数据
        serializer = self.get_serializer(page, many=True)
        return self.get_paginated_response(serializer.data)


# 评论的视图类
class CommentViewSet(ModelViewSet):
    # 指定模型和序列化器
    queryset = Comment.objects.filter(is_delete=False, article__is_delete=False, article__status=1)
    serializer_class = CommentSerializer
    # 需要登录权限
    permission_classes = [IsAuthenticated]
    # 评论进行分页
    pagination_class = ArticleLimitOffsetPagination

    def get_serializer_class(self):
        if self.action == 'retrieve':
            return SonCommentSerializer
        else:
            return CommentSerializer

    # 重写create方法,不然会导致用户id和所评论不相符
    def create(self, request, *args, **kwargs):
        # 允许修改传入的post数据
        request.POST._mutable = True
        # 写死现在的id为目前的登录用户id
        request.data['user'] = request.user.id
        return ModelViewSet.create(self, request, *args, **kwargs)

    # 展示当前一级评论下面的子级评论(重写retrieve方法)
    def retrieve(self, request, *args, **kwargs):
        # 尝试是否可以获取到当前一级评论
        try:
            comment = self.get_queryset().get(id=kwargs.get('pk'))
        except Comment.DoesNotExist:
            return Response(status=status.HTTP_404_NOT_FOUND)
        # 拿到所有子评论并分页返回
        comments = comment.parent_comment_set.all()
        page = self.paginate_queryset(comments)
        serializer = self.get_serializer(page, many=True)
        return self.get_paginated_response(serializer.data)
